import { EventEmitter } from 'events';
import Sqlite3 from 'sqlite3';
import { ICallBack, IResponse } from '../interfaces/api.interface';

export default class Log extends EventEmitter {
  private db: Sqlite3;
  status = false;

  constructor(name: string = 'log') {
    super();
    if (typeof name !== 'string') {
      console.error('Database name must be string type.');
    }
    if (!name) {
      console.error('Database name cannot be empty.');
    }
    this.init(name);
  }

  init(name: string) {
    try {
      this.db = new Sqlite3('/' + name, 'c+');
      this.status = true;
      console.info('Log database started successfully!');
    } catch (error) {
      console.error('[init]: Failed to instantiate database object');
    }
  }

  /**
   * 创建数据表
   * @param tableName 数据表名称
   * @param cb 回调
   */
  createTable(tableName: string, cb: ICallBack) {
    try {
      this.db.begin();
      this.db.run(`CREATE TABLE ${tableName}(date text, time text, value text, color text)`);
      this.db.commit();
      cb({ result: true, message: `创建数据表${tableName}成功！` });
      console.info('Datasheet created successfully!');
    } catch (error) {
      this.db.rollback();
      console.error('[createTable]: ', error);
      cb({ result: false, message: `创建数据表${tableName}失败！` });
    }
  }

  /**
   * 删除数据表
   * @param tableName 数据表名称
   * @param attemptsIndex 尝试次数
   * @param cb 回调
   */
  deleteTable(tableName: string, attemptsNum: number = 3, cb: ICallBack) {
    try {
      this.db.begin();
      this.db.run(`drop table if exists ${tableName}`);
      this.db.commit();
      cb({ result: true, message: `删除数据表${tableName}成功！` });
      console.info('Data table deleted successfully!');
    } catch (error) {
      this.db.rollback();
      if (attemptsNum > 1) {
        this.deleteTable(tableName, attemptsNum--, cb);
      } else {
        console.error('[deleteTable]:', error);
        cb({ result: false, message: `删除数据表${tableName}失败！` });
      }
    }
  }

  /**
   * 向指定数据表中插入数据
   * @param tableName 数据表名称（房间id ）
   * @param data
   * @param cb 回调
   */
  insert(tableName: string, data: { date: string; time: string; value: string; color: string }, cb: ICallBack) {
    this.queryTableContentByDate(tableName, data.date, 0, (res: IResponse) => {
      if (!res || !res.result) {
        cb({ result: false, message: res.message || '操作失败！' });
      } else {
        if (res.data.length >= 200) {
          // 这里判断处理不严谨(下面插入sql条件子语句执行出错)
          console.error('The total number of records in the datasheet exceeds the upper limit of 200.');
          cb({ result: false, message: '日志记录超出限制，请检查设备是否异常！' });
        } else {
          try {
            console.info('start insert');
            this.db.begin();
            this.db.run(`INSERT INTO ${tableName} VALUES(?, ?, ?, ?)`, data.date, data.time, data.value, data.color);
            this.db.commit();
            cb({ result: true, message: '操作成功！' });
            console.info('insert success');
          } catch (error) {
            this.db.rollback();
            cb({ result: false, message: '操作失败，请重试！' });
            console.error('[insert]: ', error);
          }
        }
      }
    });
  }

  /**
   * 从数据表中查找指定日期的日志数据
   * @param tableName 数据报名
   * @param date 指定日期
   * @param cb 回调函数
   */
  queryTableContentByDate(tableName: string, date: string, limit: number = 0, cb: ICallBack) {
    const res = this.checkTableExist(tableName);
    if (!res) {
      return cb({ result: false, message: '操作失败，请刷新重试！' });
    }
    if (!res.result) {
      return cb({ result: false, message: '数据库出现异常，请联系客服！' });
    }
    try {
      let tableData;
      if (!limit) {
        // 取数据库所有数据
        tableData = this.db[Symbol.iterator](
          `SELECT time,value,color FROM ${tableName} WHERE date = ? ORDER BY time DESC`,
          date
        );
      } else {
        tableData = this.db[Symbol.iterator](
          `SELECT time,value,color FROM ${tableName} WHERE date = ? ORDER BY time DESC LIMIT ?`,
          date,
          limit
        );
      }
      // console.log([...tableData]);
      cb({ result: true, message: '操作成功！', data: [...tableData] });
    } catch (error) {
      console.error('[queryTableContentByDate]: ', error);
      cb({ result: false, message: '查询失败，请重试！' });
    }
  }

  /**
   * 检查指定数据表是否存在
   * @param tableName 数据表名
   * @returns 检测结果
   */
  private checkTableExist(tableName: string): IResponse | undefined {
    try {
      const countIter = this.db[Symbol.iterator](
        `SELECT count(*) as num from sqlite_master WHERE type='table' and name = ? `,
        tableName
      );
      if ([...countIter][0]['num'] > 0) {
        return { result: true, message: 'Query successful.' };
      } else {
        return { result: false, message: 'Query failed.' };
      }
    } catch (error) {
      console.error('[checkTableExist]: ' + error);
    }
  }

  /**
   * 获取数据库的所有表名
   * @returns 数据库所有表名
   */
  // private getDBTableNames(): Array<{ name: string }> | undefined {
  //   try {
  //     const tables = this.db[Symbol.iterator](`SELECT name FROM sqlite_master WHERE type='table' ORDER BY name`);
  //     // console.info([...tables])
  //     return [...tables];
  //   } catch (error) {
  //     throw new Error('[getDBTableNames]: ' + error);
  //   }
  // }
}
